#include "sign_up.h"

FILE *fp_stu;
void student_account_save(FILE *fp_stu)
{    
    // 检查文本框指针有效性
    const char *account = lv_textarea_get_text(ui_TextArea5);
    const char *password = lv_textarea_get_text(ui_TextArea6);
    if (account == NULL || password == NULL) {
        lv_textarea_set_text(ui_Label16, "账号密码获取失败!");
        fclose(fp_stu);
        return;
    }
    fprintf(fp_stu, "*****************\n账号:%s\n密码:%s\n", account, password);
}

/*链表保存*/
//初始化链表
stu_datalist init_Stu_datalist()
{
    stu_datalist first = calloc(1,sizeof(stu_datanode));
    if(first == NULL)
        return NULL;
    first->next = first;
    first->prev = first;
    printf("address first:%p\n",first);
    printf("address next:%p\n",first->next);
    return first;
}

//新节点
stu_datalist node_Stu_datalist(STU students)
{
    stu_datalist new = malloc(sizeof(stu_datanode));
    if(new == NULL)
        return NULL;
    new->next = new;
    new->prev = new;
    new->student = students;
    return new;
}

//头插
void insert_head(stu_datalist head, stu_datalist new)
{
    // 同时检查head和new是否为NULL
    if(head == NULL || new == NULL)
        return;
        
    if(head->next == head && head->prev == head)
    {
        new->prev = head;
        new->next = head;
        head->next = new;
        head->prev = new;
        return;
    }
    new->prev = head;
    new->next = head->next;
    head->next->prev = new;
    head->next = new;
}
//尾插法
void tail_insert(stu_datalist head, stu_datalist new)
{
    // 同时检查head和new是否为NULL
    if(head == NULL || new == NULL)
        return;
    if(head->next == head && head->prev == head)
    {
        new->prev = head;
        new->next = head;
        head->next = new;
        head->prev = new;
        return;
    }
    new->next = head;
    new->prev = head->prev;
    head->prev->next = new;
    head->prev = new;
}
// //链表的查找
// void find_account_for_stulist(stu_datalist head, STU findStu)
// {
//     if(head == NULL) {  // 新增检查
//         error_label();
//         return;
//     }
//     stu_datalist tmp = head->next;
//     for(; tmp!=head; tmp = tmp->next)
//     {
//         if(strcmp(tmp->student.account ,findStu.account) == 0)
//         {
//             if(strcmp(tmp->student.password ,findStu.password) == 0)
//             {
//                 ui_event_Button1();
//                 return;
//             }
//             else
//                 error_label();            
//         }
//     }
//     error_label(); 
// }

void process_register(STUlist students, stu_datalist headnode)
{
    //【修复】注册时重新打开文件（全局fp_stu可能已关闭）
    FILE *fp_stu = fopen("student.txt", "a+");
    if (fp_stu == NULL)
    {
        lv_textarea_set_text(ui_Label16, "注册失败：文件打开失败!");
        state_register = false;
        return;
    }
    /*持续检测全局变量 state_register---用于清空文本框*/
    // 1. 获取文本框内容并检查是否为NULL
    const char *account_text = lv_textarea_get_text(ui_TextArea5);
    const char *password_text = lv_textarea_get_text(ui_TextArea6);
    if (account_text == NULL || password_text == NULL) {
        lv_textarea_set_text(ui_Label16, "文本框内容无效!");
        state_register = false;
        return;
    }
    // 2. 安全复制字符串（防止溢出）
    //sprintf(students.account,"%s",account_text);
    strncpy(students->account, account_text, sizeof(students->account)-1);
    students->account[sizeof(students->account)-1] = '\0';  // 强制添加结束符
    strncpy(students->password, password_text, sizeof(students->password)-1);
    students->password[sizeof(students->password)-1] = '\0';
    // 3. 创建节点并检查
    stu_datalist new = node_Stu_datalist(*students);
    if (new == NULL) {
        lv_textarea_set_text(ui_Label16, "节点创建失败！");
        state_register = false;
        return;
    }
    // 4. 插入节点（已确保head和new非空）
    tail_insert(headnode, new);
    student_account_save(fp_stu);    
    state_register = false;
    //fclose(fp_stu);   
    print_stu_list(headnode);  //同步打印链表
}
//读取账号密码保存在链表中（适配分隔线格式）
void read_stu_to_list(stu_datalist headnode)
{
    // 只读模式打开文件（无需a+，避免意外写入）
    FILE *fp_stu_read = fopen("student.txt", "r");
    if(fp_stu_read == NULL)
    {
        perror("文件打开失败");
        return; // 用return代替exit，避免程序直接退出
    }
    STU stu_read = {0};
    char line[128] = {0}; // 用于读取分隔线和空行
    while(1)
    {
        // 1. 跳过分隔线（*****************）
        if(fgets(line, sizeof(line), fp_stu_read) == NULL)
        {
            // 文件读取结束或出错
            if(feof(fp_stu_read)) break;
            else { perror("读取分隔线失败"); break; }
        }
        // 去除换行符后判断是否为分隔线
        line[strcspn(line, "\n")] = '\0';
        if(strcmp(line, "*****************") != 0)
        {
            printf("格式错误：预期分隔线，实际内容：%s\n", line);
            continue; // 跳过错误行，继续下一轮
        }
        // 2. 读取账号行（账号:xxx）
        char account[15] = {0};
        if(fgets(account, sizeof(account), fp_stu_read) == NULL)
        {
            printf("账号行缺失，跳过当前记录\n");
            break;
        }
        // 提取账号（跳过"账号:"）
        char *tmp = strstr(account, ":");
        if(tmp == NULL)
        {
            printf("账号格式错误：%s\n", account);
            continue;
        }
        char *tmp_account = tmp + 1;
        // 3. 读取密码行（密码:xxx）
        char password[12] = {0};
        if(fgets(password, sizeof(password), fp_stu_read) == NULL)
        {
            printf("密码行缺失（对应账号：%s)\n", tmp_account);
            break;
        }
        // 提取密码（跳过"密码:"）
        char *tmp2 = strstr(password, ":");
        if(tmp2 == NULL)
        {
            printf("密码格式错误：%s\n", password);
            continue;
        }
        char *tmp_password = tmp2 + 1;
        // 4. 处理字符串（去除换行符，安全复制）
        strncpy(stu_read.account, tmp_account, sizeof(stu_read.account)-1);
        stu_read.account[sizeof(stu_read.account)-1] = '\0';
        strncpy(stu_read.password, tmp_password, sizeof(stu_read.password)-1);
        stu_read.password[sizeof(stu_read.password)-1] = '\0';

        // 去除可能残留的换行符
        stu_read.account[strcspn(stu_read.account, "\n")] = '\0';
        stu_read.password[strcspn(stu_read.password, "\n")] = '\0';

        // 5. 打印验证
        printf("账号:%s\n", stu_read.account);
        printf("密码:%s\n", stu_read.password);

        // 6. 插入链表（尾插法保持顺序）
        stu_datalist new_stu = node_Stu_datalist(stu_read);
        if(new_stu != NULL)
        {
            tail_insert(headnode, new_stu);
        }
    }
    fclose(fp_stu_read); // 关闭文件
    printf("文件读取完毕\n");
}

//打印链表内容
void print_stu_list(stu_datalist headnode)
{
    if (headnode == NULL) {
        printf("链表为空（表头无效）\n");
        return;
    }

    stu_datalist tmp = headnode->next;  // 从第一个数据节点开始
    if (tmp == headnode) {  // 链表无数据
        printf("链表中无账号密码数据\n");
        return;
    }

    int count = 1;
    while (tmp != headnode) {
        printf("第%d条:账号=%-12s密码=%-15s\n", count, tmp->student.account, tmp->student.password);
        tmp = tmp->next;
        count++;
    }
}

